package com.ng.common.fileupload.storage;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.io.Serializable;
import java.util.Date;

import org.apache.commons.io.FileUtils;
import org.apache.commons.io.IOUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;

import com.ng.common.fileupload.GsFileStorage;
import com.ng.common.fileupload.entity.UploadFileInfoEntity;
import com.ng.common.fileupload.entity.UploadFileInfoEntity.StoreType;
import com.ng.common.utils.DateUtils;
import com.ng.common.utils.StringUtils;

import cn.hutool.core.lang.UUID;

/**
 * 
 * 
 * 
 * @author lyf
 * @version 1.0
 *
 */ 
@Component
@ConditionalOnProperty(prefix="ng.upload",name = "type", havingValue = "local")
public class LocalFileStorage implements GsFileStorage , Serializable {

	Logger logger = LoggerFactory.getLogger(getClass());
	
	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	
	@Value("${ng.upload.local.upload_local_path:}")
	private String path ;
	
	@Value("${ng.upload.local.server_url:}")
	private String serverUrl ;
	 
	
	public String getPath() {
		return path;
	}
	
	 
	 @Override
	 public String getType() {
		 // TODO Auto-generated method stub
		 return "local";
	 }
	
	 public LocalFileStorage() {
		// TODO Auto-generated constructor stub
	}
	
	public LocalFileStorage(String path) {
		super();
		this.path = path.endsWith("/") || path.endsWith("\\") ? path : path + "/";
		this.serverUrl = serverUrl.endsWith("/") ? serverUrl : serverUrl +  "/";
	}

	  

	@Override
	public UploadFileInfoEntity uploadFile(MultipartFile file) {
		
		String month = DateUtils.format(new Date(), "yyyyMM");

		String filename = file.getOriginalFilename();
		String suffix = StringUtils.getSuffixName(filename);


		//String contextPath = HttpContextUtils.getHttpServletRequest().getContextPath();
		

		// 文件名随机
		String currName = DateUtils.format(new Date(), "yyyyMMddHHmmssSSS") + ((int)(Math.random() * 100000) ) + "." + suffix ;


		String filePath = month + File.separator + currName ;

		File localFile = new File(path , filePath);
		if(!localFile.getParentFile().exists()) {
			boolean mkdirs = localFile.getParentFile().mkdirs();
			logger.info("mkdirs " + localFile.getParentFile().getPath() + " , result : " + mkdirs);
		}


		try {
			// 转流 校验
			byte[] bs = file.getBytes(); 
	        
	    	// 2021-09-17 lyf 增加文件格式验证 
			bs = validatorFile(bs, suffix);
			
			FileUtils.writeByteArrayToFile(localFile, bs);
			
			 
			UploadFileInfoEntity entity = new UploadFileInfoEntity();
			/*entity.setCreateDate(new Date());
			entity.setFileName(currName);
			entity.setFilePath(localFile.getPath());
			entity.setStoreType(StoreType.lcoal.ordinal());
			entity.setRealName(filename);
			*/
			
			String fileId = UUID.fastUUID().toString().replace("-", "");
			entity.setId(fileId);
			entity.setCreateTime(new Date());
			entity.setOldFileName(filename);
			entity.setNewFileName(filePath);
			entity.setFileUrl(serverUrl + "/file/fileDown?uuid=" + fileId);
			entity.setFileSize(file.getSize());
			entity.setFileSuffix(suffix);
			entity.setStoreType(StoreType.lcoal.ordinal());
		 
			return entity;
			
		} catch (IllegalStateException | IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		
		
		return null;
	}


	@Override
	public void downFile(UploadFileInfoEntity entity, OutputStream out) {
		
		File file = new File(path , entity.getNewFileName());
		 
		if(file.exists()) {
			try {
				IOUtils.copy(new FileInputStream(file), out, 8 * 1024);
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		
		
	}


	@Override
	public boolean deleteFile(UploadFileInfoEntity entity) {
		File file = new File(path , entity.getNewFileName());
		 
		if(file.exists()) {
			
			return file.delete();
		}
		
		return false;
		
	}




	@Override
	public UploadFileInfoEntity uploadFile(File file) {
		 String month = DateUtils.format(new Date(), "yyyyMM");
	        
			
			File dirFile = new File(path , month);
			if(!dirFile.exists()) {
				boolean mkdirs = dirFile.mkdirs();
				logger.info("mkdirs " + dirFile.getPath() + " , result : " + mkdirs);
			}
			
			String filename = file.getName();
			
			String suffix = StringUtils.getSuffixName(filename);
			
			// 文件名随机
			String currName = DateUtils.format(new Date(), "yyyyMMddHHmmssSSS") + ((int)(Math.random() * 100000) ) + "." + suffix ;
		
			
			File localFile = new File(dirFile , currName);
			
			try {
				byte[] bs = FileUtils.readFileToByteArray(file);
		        
		    	// 2021-09-17 lyf 增加文件格式验证 
				bs = validatorFile(bs, suffix);
				
				FileUtils.writeByteArrayToFile(localFile, bs);
				 
				
				UploadFileInfoEntity entity = new UploadFileInfoEntity();

				entity.setCreateTime(new Date());
				entity.setOldFileName(filename);
				entity.setNewFileName(currName);
				entity.setFileUrl(localFile.getPath());
				entity.setFileSize(file.length());
				entity.setStoreType(StoreType.lcoal.ordinal());
			 
				return entity;
				
			} catch (IllegalStateException | IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			
			
			
			return null;
	}
	
	
	

}
